//
// Copyright (C) 2024 Kumo inc.
// Author: Jeff.li lijippy@163.com
// All rights reserved.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as published
// by the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with this program.  If not, see <https://www.gnu.org/licenses/>.
//

#include <hadarservice/engine.h>
#include <turbo/log/logging.h>

namespace hadarservice {

    ConvertEngine &ConvertEngine::instance() {
      static ConvertEngine instance;
      return instance;
    }

    void ConvertEngine::assert_initialized() {
        LOG_IF(FATAL, !initialized_)<<"Engine not have been initialized";
    }

    turbo::Status ConvertEngine::initailize(const std::string & dict_path) {
        LOG_IF(FATAL, initialized_)<<"Engine already initialized";
        std::vector<std::string> roots = {dict_path};
        try {
          hk2s_ = std::make_unique<hadar::SimpleConverter>("hk2s.json", roots);
        } catch (const std::exception & e) {
          return turbo::not_found_error("not fount %s config", "hk2s.json");
        }
        try {
            hk2t_ = std::make_unique<hadar::SimpleConverter>("hk2t.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "hk2t.json");
        }
        try {
            jp2t_ = std::make_unique<hadar::SimpleConverter>("jp2t.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "jp2t.json");
        }
        try {
            s2hk_ = std::make_unique<hadar::SimpleConverter>("s2hk.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "s2hk.json");
        }
        try {
            s2t_ = std::make_unique<hadar::SimpleConverter>("s2t.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "s2t.json");
        }
        try {
            s2tw_ = std::make_unique<hadar::SimpleConverter>("s2tw.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "s2tw.json");
        }
        try {
            s2twp_ = std::make_unique<hadar::SimpleConverter>("s2twp.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "s2twp.json");
        }
        try {
            t2hk_ = std::make_unique<hadar::SimpleConverter>("t2hk.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "t2hk.json");
        }
        try {
            t2jp_ = std::make_unique<hadar::SimpleConverter>("t2jp.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "t2jp.json");
        }
        try {
            t2s_ = std::make_unique<hadar::SimpleConverter>("t2s.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "t2s.json");
        }
        try {
            t2tw_ = std::make_unique<hadar::SimpleConverter>("t2tw.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "t2tw.json");
        }
        try {
            tw2s_ = std::make_unique<hadar::SimpleConverter>("tw2s.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "tw2s.json");
        }
        try {
            tw2sp_ = std::make_unique<hadar::SimpleConverter>("tw2sp.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "tw2sp.json");
        }
        try {
            tw2t_ = std::make_unique<hadar::SimpleConverter>("tw2t.json", roots);
        } catch (const std::exception & e) {
            return turbo::not_found_error("not fount %s config", "tw2t.json");
        }
      initialized_ = true;
      return turbo::OkStatus();
    }

    turbo::Result<std::string> ConvertEngine::hk2s(const std::string & message) {
        assert_initialized();
        try {
            return hk2s_->Convert(message);
        } catch (const std::exception & e) {
           return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::hk2t(const std::string & message) {
        assert_initialized();
        try {
            return hk2t_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::jp2t(const std::string & message) {
        assert_initialized();
        try {
            return jp2t_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::s2hk(const std::string & message) {
        assert_initialized();
        try {
            return s2hk_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::s2t(const std::string & message) {
        assert_initialized();
        try {
            return s2t_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }


    turbo::Result<std::string> ConvertEngine::s2tw(const std::string & message) {
        assert_initialized();
        try {
            return s2tw_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::s2twp(const std::string & message) {
        assert_initialized();
        try {
            return s2twp_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }


    turbo::Result<std::string> ConvertEngine::t2hk(const std::string & message) {
        assert_initialized();
        try {
            return t2hk_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::t2jp(const std::string & message) {
        assert_initialized();
        try {
            return t2jp_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::t2s(const std::string & message) {
        assert_initialized();
        try {
            return t2s_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::t2tw(const std::string & message) {
        assert_initialized();
        try {
            return t2tw_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::tw2s(const std::string & message) {
        assert_initialized();
        try {
            return tw2s_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::tw2sp(const std::string & message) {
        assert_initialized();
        try {
            return tw2sp_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

    turbo::Result<std::string> ConvertEngine::tw2t(const std::string & message) {
        assert_initialized();
        try {
            return tw2t_->Convert(message);
        } catch (const std::exception & e) {
            return turbo::unavailable_error(e.what());
        }
    }

}